﻿using System;
using System.ComponentModel;
using System.Reflection;
using System.Windows.Forms;

namespace PatersonTech
{
	class AdjustablePropertyGrid : PropertyGrid
	{
		const BindingFlags BindFlags = BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic;


		#region Public Properties
		
		/// <summary>
		/// Gets or sets the width of the label column, in pixels.
		/// </summary>
		[Browsable(false)]
		public int LabelWidth
		{
			get
			{
				try
				{
					object gridView = GetGridView();
					Type type = gridView.GetType();
					PropertyInfo pi = type.GetProperty("InternalLabelWidth", BindFlags);
					object InternalLabelWidth = pi.GetValue(gridView, BindingFlags.GetProperty, null, null, null);
					return (int)InternalLabelWidth;
				}
				catch
				{
					return 0;
				}
			}

			set
			{
				try
				{
					object gridView = GetGridView();
					Type type = gridView.GetType();
					MethodInfo mi = type.GetMethod("MoveSplitterTo", BindFlags);
					mi.Invoke(gridView, new Object[] { value });
				}
				catch
				{
				}
			}
		}

		/// <summary>
		/// Gets or sets the height of the help region, in lines.
		/// </summary>
		[Browsable(false)]
		public int HelpRegionSize
		{
			get
			{
				try
				{
					Control ctl = GetHelpRegion();
					PropertyInfo pi = ctl.GetType().GetProperty("Lines");
					return (int)pi.GetValue(ctl, null);
				}
				catch
				{
					return 0;
				}
			}

			set
			{
				try
				{
					Control ctl = GetHelpRegion();
					Type type = ctl.GetType();
					PropertyInfo pi = type.GetProperty("Lines");
					pi.SetValue(ctl, value, null);
					FieldInfo fi = type.BaseType.GetField("userSized", BindFlags);
					fi.SetValue(ctl, true);
				}
				catch
				{
				}
			}
		}
		#endregion


		#region Private Methods

		private object GetGridView()
		{
			Type type = this.GetType().BaseType;
			FieldInfo fi = type.GetField("gridView", BindFlags);
			return fi.GetValue(this);
		}

		private Control GetHelpRegion()
		{
			Type type = this.GetType().BaseType;
			PropertyInfo pi = type.GetProperty("Controls");
			ControlCollection cc = (ControlCollection)pi.GetValue(this, null);
			foreach (Control ctl in cc)
			{
				type = ctl.GetType();
				if (type.Name == "DocComment")
					return ctl;
			}
			return null;
		}

		#endregion
	}
}
